﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Huirui.Cavan.Application.MainBoundedContext.SystemModule;
using Huirui.Cavan.Domain.MainBoundedContext.PurchaseModule;
using Huirui.Cavan.Domain.MainBoundedContext.SearchModule;
using Huirui.Cavan.Domain.MainBoundedContext.SystemModule;
using Huirui.Cavan.Domain.Seedwork;
using Huirui.Cavan.Core.Extension;
using Huirui.Cavan.Domain.MainBoundedContext.FinanceModule;
using Spring.Context.Support;
using Huirui.Cavan.Domain.MainBoundedContext.ReportModule;
using System.Collections;

namespace Huirui.Cavan.Application.MainBoundedContext.PurchaseModule
{
    public class PayAppService : BaseAppService<Pay, string, PaySearch, IPayRepository>, IPayAppService
    {
        private IUnPayAppService UnPayAppService { get; set; }
        private IAccountAppService AccountAppService { get; set; }
        private ISupplierAppService SupplierAppService { get; set; }

        public override BoolGenericResult<Pay> AddOrUpdate(Pay entity)
        {
            Init();
            BoolGenericResult<Pay> result = new BoolGenericResult<Pay>();

            this.UnPayAppService = this.SpringContext.GetObject(PurchaseModuleConst.UNPAYAPPSERVICE) as IUnPayAppService;
            this.AccountAppService = this.SpringContext.GetObject(SystemModuleConst.ACCOUNTAPPSERVICE) as IAccountAppService;
            this.SupplierAppService = this.SpringContext.GetObject(SystemModuleConst.SUPPLIERAPPSERVICE) as ISupplierAppService;
            Employee employee = this.EmployeeAppService.GetSingleBySearch(SearchFactory.CreateEmployeeSearch(SecurityAppService.UserAccount.Id));
            Accountant accountant = new Accountant(employee);

            Pay oldPay = null;
            if (entity.Id.IsNotEmpty())
            {
                oldPay = this.Repository.Get(entity.Id);
            }
            if (entity.FromAccount.IsNotNull() && entity.FromAccount.Id.IsNotEmpty())
            {
                entity.FromAccount = this.AccountAppService.GetById(entity.FromAccount.Id);
            }
            if (entity.Supplier.IsNotNull() && entity.Supplier.Id.IsNotEmpty())
            {
                entity.Supplier = this.SupplierAppService.GetById(entity.Supplier.Id);
            }
            foreach (PayDetail pd in entity.PayDetails)
            {
                pd.UnPay = this.UnPayAppService.GetById(pd.UnPay.Id);
            }
            if (oldPay.IsNull())
            {
                IIDGenerateAppService idGenerateAppService = this.SpringContext.GetObject(SystemModuleConst.IDGENERATEAPPSERVICE, new object[] { employee.Corporation }) as IIDGenerateAppService;
                entity.Id = idGenerateAppService.GenerateID(SystemIdentifier.ReceiptCodeRuleType.Pay);

                result = accountant.Pay(entity.Id, entity.PayDate, entity.FromAccount, entity.AccountNumber, entity.Amount, entity.Discount, entity.Currency, entity.CurrencyRate, entity.Remark,
                    employee, entity.Supplier, entity.PayDetails);
                if (result.IsSuccess)
                {
                    foreach(PayDetail pd in entity.PayDetails)
                    {
                        this.UnPayAppService.Update(pd.UnPay);
                    }
                   
                    result = base.Add(result.Object);
                }
            }
            else
            {
                result = accountant.RePay(oldPay, entity.PayDetails);
                if (result.IsSuccess)
                {
                    foreach (PayDetail pd in entity.PayDetails)
                    {
                        this.UnPayAppService.Update(pd.UnPay);
                    }
                    result = base.Update(oldPay);
                }
            }
            return result;
        }

        public IList<UnPayAndPayReport> GetUnPayAndPayReport(DateTime? startDate, DateTime? endDate, string supplierCode, int maxRowsPerPage, int currentPage)
        {
            return this.Repository.GetUnPayAndPayReport(startDate, endDate, supplierCode, maxRowsPerPage, currentPage);
        }

        public IList<PayReport> GetPayReport(string payCode, DateTime? startDate, DateTime? endDate, string supplierCode)
        {
            return this.Repository.GetPayReport(payCode, startDate, endDate, supplierCode);
        }

    }
}
